package com.gitee.l0km.jsonvisitor.pairmatcher;

import java.util.Stack;

import org.antlr.v4.runtime.Token;

import static com.google.common.base.Preconditions.checkArgument;
import static com.google.common.base.Preconditions.checkState;

import com.gitee.l0km.jsonvisitor.parser.JsonPairLexer;
import com.gitee.l0km.jsonvisitor.parser.JsonPairParser;
import com.gitee.l0km.jsonvisitor.utils.InterpreterUtils;

import static com.gitee.l0km.jsonvisitor.utils.CharStreamSupport.lexerOf;
import static com.gitee.l0km.jsonvisitor.utils.CharStreamSupport.asCharStream;

public class JsonPairMatcher0 {

	/**
	 * 创建ANTLR4生成的解析器对象{@link JsonPairParser}
	 * @param input 待解析的数据
	 */
	public static JsonPairLexer jsonPairLexerOf(Object input) {
		return lexerOf(asCharStream(input), JsonPairLexer.class);
	}

	/**
	 * 跳过当前值对
	 * @param lexer
	 * @param stack
	 */
	private static void skipPair(JsonPairLexer lexer, Stack<Integer> stack) {
			Token t;
			while ((t = lexer.nextToken()).getType() != Token.EOF) {
	//			log("{}:{}",JsonPairLexer.VOCABULARY.getSymbolicName(t.getType()),t.getText());
				if(stack.isEmpty()) {
					if (t.getType() == JsonPairLexer.COMMA || t.getType()==JsonPairLexer.RBRACE) {
						return;
					}
				}
				switch (t.getType()) {
				case JsonPairLexer.LBRACE:
				case JsonPairLexer.LBRACKET:
					stack.push(t.getType());
					break;
				case JsonPairLexer.RBRACE: 
					checkState(stack.pop() == JsonPairLexer.LBRACE,"MISMATCH TOKEN,%s REUIRED",
							JsonPairLexer.VOCABULARY.getSymbolicName(JsonPairLexer.LBRACE));
					break;
				case JsonPairLexer.RBRACKET: 
					checkState(stack.pop() == JsonPairLexer.LBRACKET,"MISMATCH TOKEN,%s REUIRED",
							JsonPairLexer.VOCABULARY.getSymbolicName(JsonPairLexer.LBRACKET));
					break;
				default:
					break;
				}
			}
		}

	public static String matchPair(JsonPairLexer lexer) {
		Token t = lexer.nextToken();
		if (JsonPairLexer.LBRACE == t.getType()) {
			while ((t = lexer.nextToken()).getType() != Token.EOF && t.getType()!=JsonPairLexer.RBRACE) {
				//				log("{}:{}",JsonPairLexer.VOCABULARY.getSymbolicName(t.getType()),t.getText());
				Token key = t;
				checkArgument(key.getType() == JsonPairLexer.STRING, "INVALID token,%s REQUIRED",
						JsonPairLexer.VOCABULARY.getSymbolicName(JsonPairLexer.STRING));
				if(key.getText().equals("\"tokenId\"")) {
					Token colon = lexer.nextToken();
					checkArgument(colon.getType() == JsonPairLexer.COLON, "INVALID token,%s REQUIRED",
							JsonPairLexer.VOCABULARY.getSymbolicName(JsonPairLexer.COLON));
					Token value = lexer.nextToken();
					checkArgument(value.getType() != Token.EOF, "UNEXPECT EOF");
					if(value.getType() == JsonPairLexer.STRING) {
						return InterpreterUtils.unquote(value.getText());
					}
				}else {
					skipPair(lexer,new Stack<Integer>());
				}
			}
		}
		return null;
	}
	public static String matchPair(Object input) {
		return matchPair(jsonPairLexerOf(input));
	}
}

